﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using GalaSoft.MvvmLight;
using System.Collections.ObjectModel;
using Medecine.DataAccess.Patients;
using GalaSoft.MvvmLight.Command;
using Medecine.Interface.Main;
using Medecine.Interface.Properties;
using GalaSoft.MvvmLight.Messaging;
using Medecine.Dbo;
using System.Reactive.Linq;
using Medecine.Interface.Utils;

namespace Medecine.Interface.Patients
{
	public class PatientListViewModel : ViewModelWithErrors
	{
		public PatientListViewModel()
		{
			_addPatientCommand = new RightCommand(AddPatient, ViewModelLocator.MainStatic.CanInvokeCommand);
			_deletePatientCommand = new RightCommand<PatientViewModel>(DeletePatient, CanDeletePatient);
		}

		private readonly ObservableCollection<PatientViewModel> _patientList = new ObservableCollection<PatientViewModel>();
		public ObservableCollection<PatientViewModel> PatientList { get { return _patientList; } }

		public void LoadPatientList()
		{
			using (ServicePatientClient service = new ServicePatientClient())
			{
				foreach (Patient patient in service.GetListPatient())
				{
					PatientList.Add(new PatientViewModel(patient));
				}
			}
		}

		#region Add patient

		private AddPatientViewModel _addPatientViewModel = null;

		private readonly RightCommand _addPatientCommand = null;
		public RightCommand AddPatientCommand { get { return _addPatientCommand; } }

		private void AddPatient()
		{
			_addPatientViewModel = new AddPatientViewModel();
			Messenger.Default.Send(new GoToViewMessage(ViewName.AddPatient, _addPatientViewModel, AddPatientCompleted));
		}

		private void AddPatientCompleted()
		{
			if (_addPatientViewModel.Cancelled == false)
			{
				_patientList.Add(new PatientViewModel(_addPatientViewModel.Patient));
			}

			_addPatientViewModel.Cleanup();
			_addPatientViewModel = null;
		}

		#endregion // Add patient

		#region Delete patient

		private readonly RightCommand<PatientViewModel> _deletePatientCommand = null;
		public RightCommand<PatientViewModel> DeletePatientCommand { get { return _deletePatientCommand; } }

		private bool CanDeletePatient(PatientViewModel patient)
		{
			return (patient != null) && ViewModelLocator.MainStatic.CanInvokeCommand();
		}

		private void DeletePatient(PatientViewModel patient)
		{
			using (ServicePatientClient service = new ServicePatientClient())
			{
				Observable.FromAsyncPattern<int, bool>(service.BeginDeletePatient, service.EndDeletePatient)
					.Invoke(patient.Id)
					.ObserveOnDispatcher()
					.Subscribe(
						(b) => DeletePatientCompleted(patient, b),
						(e) => Messenger.Default.Send(new ErrorMessage(e.Message)));
			}
		}

		private void DeletePatientCompleted(PatientViewModel patient, bool result)
		{
			if (result == true)
				PatientList.Remove(patient);
			else
				Messenger.Default.Send(new ErrorMessage(Resources.DeletePatientError));

		}

		#endregion // Delete patient
	}
}
